﻿using MQTTnet.Client;
using System;
using System.IO.Ports;
using System.Windows.Forms;
using System.Configuration;
using System.Threading;
using System.Runtime.ConstrainedExecution;
using System.Collections.Generic;
using MQTTnet;
using Newtonsoft.Json;
using System.IO;
using MQTTnet.Server;


namespace JHQC2
{
    public partial class OptForm : Form
    {
        SerialPort ser_data;
        string mqttTopic;
        IMqttClient mqttClient;
        MqttClientOptionsBuilder optionsBuilder;
        string logPath;
        string fullscreen = "false";
        string v1 = "";
        string v2 = "";
        string v3 = "";
        string v4 = "";
        string v5 = "";
        public OptForm()
        {
            logPath = "./" + DateTime.Now.ToString("yyMMdd") + ".log";
            InitializeComponent();
            Configuration config = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);
            var data_com = config.AppSettings.Settings["data"].Value;
            fullscreen = config.AppSettings.Settings["fullscreen"]?.Value;
            if (fullscreen == "true")
            {
                this.WindowState = FormWindowState.Maximized;
                this.TopMost = true;
            }
            ser_data = new SerialPort(data_com, 9600, Parity.None, 8, StopBits.One);
            ser_data.WriteTimeout=3000;
            var factory = new MqttFactory();
            mqttClient = factory.CreateMqttClient();
            optionsBuilder = new MqttClientOptionsBuilder()
              .WithTcpServer(config.AppSettings.Settings["mqttServer"].Value);
            var user = config.AppSettings.Settings["mqttUid"].Value;
            var pwd = config.AppSettings.Settings["mqttPwd"].Value;
            mqttTopic = config.AppSettings.Settings["mqttTopic"].Value;
            if (!String.IsNullOrEmpty(user) && !String.IsNullOrEmpty(pwd))
                optionsBuilder.WithCredentials(user, pwd);
        }

        public async void GetData()
        {
            try
            {
                ser_data.Open();
                byte[] sendData = System.Text.Encoding.ASCII.GetBytes("$001?RES1,A-Z%");
                ser_data.Write(sendData, 0, sendData.Length);
                Thread.Sleep(300);
                string receive = ser_data.ReadExisting();
                if (receive.Length == 0) return;
                File.AppendAllText(logPath, "S1:" + receive + "\n");
                string[] receiveArr = receive.Split(',');
                string[] result = { receiveArr[4], receiveArr[5], receiveArr[6], receiveArr[8], "" };

                sendData = System.Text.Encoding.ASCII.GetBytes("$001?RES1,a-z%");
                ser_data.Write(sendData, 0, sendData.Length);
                Thread.Sleep(300);

                receive = ser_data.ReadExisting();
                File.AppendAllText(logPath, "S2:" + receive + "\n");
                receiveArr = receive.Split(',');
                result[4] = receiveArr[3];
                Dictionary<string, object> data = new Dictionary<string, object>
                {
                    { "条码",label9.Text},
                    { "电压", result[0] },
                    { "电流", result[1] },
                    { "功率", result[2] },
                    { "频率", result[3] },
                    { "时间", result[4] },
                };
                string json = JsonConvert.SerializeObject(data);
                int retry = 0;
                MqttClientConnectResultCode connectStatus = MqttClientConnectResultCode.NotAuthorized;
                while (connectStatus != MqttClientConnectResultCode.Success && retry < 3)
                {
                    var r = await mqttClient.ConnectAsync(optionsBuilder.Build());
                    connectStatus = r.ResultCode;
                    
                    retry++;
                    if (retry == 3 && connectStatus != MqttClientConnectResultCode.Success)
                    {
                        throw new Exception("MQTT连接失败:" + r.ReasonString);
                    }
                    Thread.Sleep(10);
                }
                bool isSuccess = false;
                retry = 0;
                while (!isSuccess && retry<3)
                {
                    var publishStatus = await mqttClient.PublishStringAsync(mqttTopic, json);
                    isSuccess = publishStatus.IsSuccess;
                    retry++;
                    if (retry == 3 && !isSuccess)
                    {
                        throw new Exception("MQTT发布失败:" + publishStatus.ReasonString);
                    }
                    Thread.Sleep(10);
                }
                v1 = result[0];
                v2 = result[1];
                v3 = result[2];
                v4 = result[3];
                v5 = result[4];
                var action = new Action(() => { UpdateInfo(); });
                if (label3.InvokeRequired || label7.InvokeRequired
                    || label6.InvokeRequired || label8.InvokeRequired
                    || label11.InvokeRequired)
                {
                    label3.Invoke(action);
                }
                else
                {
                    UpdateInfo();
                }
            }
            catch (Exception e)
            {
                MessageBox.Show(e.Message);
            }
            finally
            {
                ser_data.Close();
                await mqttClient.DisconnectAsync();
            }
        }

        private void textBox1_TextChanged(object sender, EventArgs e)
        {

        }

        private void button1_Click(object sender, EventArgs e)
        {
            label9.Text = textBox1.Text;
            textBox1.Clear();
            GetData();

        }
        void UpdateInfo()
        {
            label3.Text = v1;
            label11.Text = v2;
            label6.Text = v3;
            label7.Text = v4;
            label8.Text = v5;
        }
        ~OptForm()
        {
        }
    }
}
